/* ______  __ _        _           _______                       _ _
  ------/\ \ (_)_ __  (_) __ _	  ------/_\  ___ ___  __ _ _   _| | |_
 ------/  \/ / | '_ \ | |/ _` |	 ------//_\\/ __/ __|/ _` | | | | | __|
------/ /\  /| | | | || | (_| |	------/  _  \__ \__ \ (_| | |_| | | |_
______\_\ \/ |_|_| |_|/ |\__,_|	______\_/ \_/___/___/\__,_|\__,_|_|\__|
                     |__/
	   ___________________________________________
	  /                                        /  \
	 /                                        /__  |
	|	Ninja Assault                        | /_\_|
	| 	Team: TNA                            |// \\
	|	Engine: Scuvry v0.1                  ||___||
	|	Genre: Action, Adventure, CO-OP      ||   ||
	|	Created: June 2, 2007                ||   ||
	 \   Last Update: 6/17/09                 \\_//
	  \________________________________________\_/

*/

#include <irrlicht.h>
#include <iostream>
#include "scenetype.h"
#include "HUD.h"
#include "GUI.h"
#include "input.h"
#include "usermovement.h"

using namespace irr;
using namespace core;
using namespace video;
using namespace scene;
using namespace std;

int main()
{
	SmoothEventReceiver*	receiver = SmoothEventReceiver.createReceiver();

	//Load Profile From Directory
	if( ! info )
		profile	*info = new profile;
	else
	{
		//Read Saved Profile
		if( info->Name ) 
		//Write Default Profile
		else
		{
			info->Name		= "NinjaAssault";
			info->Mesh		= "media/Ninja Actor.b3d";
			info->Skill	= "Assasin";		
		}	
	}
	
	IrrlichtDevice*	device = createDevice( profile::Video::DriverType,
		dimension2d<s32>( 640, 480 ), 16, false, false, false, &receiver );
	
	if( device == 0 )
		return 1; // could not create selected driver.
	
	array<SJoystickInfo> joystickInfo;
	if( device->activateJoysticks( joystickInfo ))
	{
		cout << "Joystick support is enabled and " << joystickInfo.size() << " joystick(s) are present." << endl;

		for( u32 joystick = 0; joystick < joystickInfo.size(); ++joystick)
		{
			cout << "Joystick " << joystick << ":" << endl;
			cout << "\tName: '" << joystickInfo[joystick].Name.c_str() << "'" << endl;
			cout << "\tAxes: " << joystickInfo[joystick].Axes << endl;
			cout << "\tButtons: " << joystickInfo[joystick].Buttons << endl;

			cout << "\tHat is: ";

			switch( joystickInfo[joystick].PovHat )
			{
			case SJoystickInfo::POV_HAT_PRESENT:
				cout << "present" << endl;
				break;

			case SJoystickInfo::POV_HAT_ABSENT:
				cout << "absent" << endl;
				break;

			case SJoystickInfo::POV_HAT_UNKNOWN:
			default:
				cout << "unknown" << endl;
				break;
			}
		}
	}
	else
	{
		cout << "Joystick support is not enabled." << endl;
	}

	stringw tmp = L"Ninja Assault v0.1(";
	tmp += joystickInfo.size();
	tmp += " joysticks)";
	device->setWindowCaption( tmp.c_str());

	IVideoDriver*		driver	= device->getVideoDriver();
	ISceneManager*		smgr	= device->getSceneManager();
	IGUIEnvironment*	env		= device->getGUIEnvironment();

	while( device->run())
	{
		driver->beginScene( true, true, SColor( 255, 106, 181, 255 ));
		
		//Game State
		switch( GamSte )
		{
			//Introduction
			case "Introduction":

				break;
			//Loading
			case "Loading":
				map*		game = map::Initialize(
					profile::Lineup,)

				RPGCamera*	camera = RPGCamera::Initialize(
					null,
					null,
					"Spectate",
					info->View[0] );
				user*		player = user::Initialize(
					null,
					null,
					info->Mesh,
					info->Name,
					info->Skill,
					info->Weapon,
					info->Item );
				//camera->
				break;

			//Playing
			case "Playing":
				//Update Movement
				player.Update();
				
				//Update Camera
				RPGCamera.Update();
				//Line.setLineFromVects( Cam.Node.getAbsolutePosition(),
				//	Line.getStart().Plus(( Cam.Node.getTarget().Minus( Line.getStart())).normalize().Mult( 1000.0 )));
				
				//If( smgr.getSceneCollisionManager().getCollisionPoint(
				//	Line, Slc, Intersection, Tri ))
				//{
				//	driver->SetTransform( ETS_WORLD, Matrix4.create());
				//	driver->draw3DTriangle( user.Tri, Null );
				//}
				
				//Calculate Scene
				projectile.Update();
				
				//Render Scene
				smgr->drawAll();
				
				//Render HUD
				InfoHUD( Amm, Hth, WpnInf, ItmInf, AphInd, ActTmr, ActAcc, Eqp );
				
				//Render GUI
				//env.drawAll();
				break;

			//Accomplished
			case "Accomplished":
				
			//Failed
			case "Failed":
				
			//Paused
			case "Paused":
				env.drawAll();
				break;
			//Spectating
			case "Spectating":
			
			//Dead
			case "Dead":
			default:
		}
		
		if( profile.Debug )
		{
			FPS = driver->getFPS();
			if( LastFPS || FPS ) LastFPS = FPS;
			
			string Str = "Ninja Assault - Irrlicht v1.5";
			string Str += " [ " + driver->getName() + " ]";
			string Str += " | FPS: " + LastFPS;
			
			vector3df UsrPos2 = user.Nde.getAbsolutePosition();
			vector3df CamPos2 = RPGCamera.Nde.getAbsolutePosition();
			float CamDstHrz2 = vector3df( UsrPos2.getX(), 0, UsrPos2.getZ()).getDistanceFrom( vector3df( CamPos2.getX(), 0, CamPos2.getZ()));
			float CamDstVrt2 = CamPos2.getY() - UsrPos2.getY();
			float FwdAng2 = vector2df( CamPos2.getX() - UsrPos2.getX(), CamPos2.getZ() - UsrPos2.getZ()).getAngle();
			
			string Str2 = "SrfAng: " + int( SrfAngTst );
			string Str2 += " | TriCnt: " + driver->getPrimitiveCountDrawn();
			//Str2$ += " | Spd: " + Vector2df.createFromVals( user.Vel.getX(), user.Vel.getZ()).getLength();
			//Str2$ += " | NdeRot: " + user.Nde.GetRotation().getY();
			//Str2$ += " | MotVelRot: " + MotVelTst.getY();
			//Str2$ += " | MotVelAng: " + Int( MotVelTst.getX()) + ", " + Int( MotVelTst.getY()) + ", " + Int( MotVelTst.getZ());
			string Str2 += " | LndPos: " + int( LndPosTst.getX()) + ", " + int( LndPosTst.getY()) + ", " + int( LndPosTst.getZ());
			//Str2$ += " | CrsAng: " + CrsAng;
			//Str2$ += " | TriNrm: " + TriNrm.normalize().getX() + ", " + TriNrm.normalize().getY() + ", " + TriNrm.normalize().getZ();
			//Str2$ += " | Landed: " + FallTest;
			//Str2$ += " | Bumped: " + BumpTest;
			//Str2$ += " | FwdAng: " + FwdAng2;
			//Str2$ += " | AphInd: " + AphInd[1];
			//Str2$ += " | ActTmr: " + ActTmr[0];
			//Str2$ += " | Prj: " + projectile.Cnt.Count();
			//Str2$ += " | CamDstHrz: " + CamDstHrz2;
			//Str2$ += " | CamDstVrt: " + CamDstVrt2;
			//Str2$ += " | NdeRot: " + user.Nde.GetRotation().getY();
			//Str2$ += " | Position: " + Int( user.Nde.getPosition().getX()) + ", "  + Int( user.Nde.getPosition().getY()) + ", " + Int( user.Nde.getPosition().getZ());
			string Str2 += " | State: " + user.Ste;
			string Str2 += " | Vel: " + int( user.Vel.getX()) + ", " + int( user.Vel.getY()) + ", " + int( user.Vel.getZ());
			
			//Render Debug Information
			SMaterial LinMat = SMaterial.Create();
			
			LinMat.setFlag( EMF_LIGHTING, False );
			driver->setMaterial( LinMat );
			
			driver->draw3DTriangle( user.Tri, _SCOLOR( 255, 255, 255, 255 ));
			driver->draw3DLine( user.Nde.getAbsolutePosition(), user.Nde.getAbsolutePosition().Plus( user.Vel.Mult( 20 )), _SCOLOR( 255, 255, 0, 0 ));
			driver->draw3DLine( user.Nde.getAbsolutePosition(), user.Nde.getAbsolutePosition().Minus( MotVelTst ), _SCOLOR( 255, 0, 0, 255 ));
			driver->draw3DLine( user.Nde.getAbsolutePosition(), LndPosTst, SColor.createFromVals( 255, 0, 255, 0 ));
			GUIFont.Draw( Str,
				rect<s32>( 0, 0, 256, 12 ),
				SColor( 255, 255, 255, 255 ));
			GUIFont.Draw( "Debug Information:",
				rect<s32>( 0, 12, 256, 24 ),
				SColor( 255, 255, 255, 255 ));
			GUIFont.Draw( Str2,
				rect<s32>( 0, 24, 256, 36 ),
				SColor( 255, 255, 255, 255 ));
		}
		driver->EndScene();
	}
	device->drop();

	return 1;
};
